/*
 * rd_interface.cpp
 *
 *  Created on: 2019-6-12
 *      Author: root
 */


#include "rd_interface.h"
#include "database.h"
#include "ffs.h"
#include "app_debug_main.h"
#include "string.h"
#include "meter_ql.h"
#include "program.h"
#include "meter_com.h"
#include "string.h"
#include <stdlib.h>
#include "log_main.h"

#ifdef QL_CLOUD_CLIENT

extern Charge_Arg g_charge_arg[GUN_NUM];   // 充电信息

extern tran_record_ql  cur_record[GUN_NUM];

int SaveRdNand(u8 gunno, u8 flag_finished, TDateTime *pdatetime) {
	tran_record_nand_ql   rdnand;
	tran_record_nand_ql_h rdnand_h;
	int offset;
	int count;
	int len;
	int fid;
	int i;
	int start;
	u16 days;
	u8 flag = 0;
	u8 ret = 0;
	Cur_FeeCfg cur_feecfg;

	u8 flagflag=0;
    
    if(gunno>7)
    	gunno=7;
    
	if (flag_finished == _MSG_SAVE_START_) {
		fid = FILE_ID_FEECFG;

		start = FEECFG_START+ sizeof(Cur_FeeCfg)*gunno;
    
		count = app_fs_read(fid, start, sizeof(Cur_FeeCfg), (u8*) &cur_feecfg);
		if (count == sizeof(Cur_FeeCfg) && cur_feecfg.flag == 0xaa55) {

			printf("读到了费率参数！！！！\r\n");
			if (memcmp((u8*) &cur_feecfg.feecfg,
					(u8*) &g_charge_arg[gunno].fee_config,
					sizeof(ql_fee_config) != 0)) {
				printf("读到了费率参数,但看来平台重新下发过，需要重新保存！！！！\r\n");
				flag = 1;
			}
			else
				printf("读到了费率参数，并有效！！！！\r\n");
		} else {
			printf("之前没有下发过费率参数，需要保存！！！！\r\n");
			flag = 1;
		}
        
		if (flag == 1) {
			cur_feecfg.flag = 0xaa55;
			cur_feecfg.feecfg = g_charge_arg[gunno].fee_config;
			count = app_fs_write(fid, start, sizeof(Cur_FeeCfg),
					(u8*) &cur_feecfg);

		}
	}


	switch(gunno)
	{
	case 0:
		fid = FILE_ID_CHARGE_RD_0;
		break;
	case 1:
		fid = FILE_ID_CHARGE_RD_1;
		break;
	case 2:
		fid = FILE_ID_CHARGE_RD_2;
		break;
	case 3:
		fid = FILE_ID_CHARGE_RD_3;
		break;
	case 4:
		fid = FILE_ID_CHARGE_RD_4;
		break;

	case 5:
		fid = FILE_ID_CHARGE_RD_5;

		break;
	case 6:
		fid = FILE_ID_CHARGE_RD_6;

		break;

	case 7:
		fid = FILE_ID_CHARGE_RD_7;
		break;
	default:
		fid = FILE_ID_CHARGE_RD_7;
		break;




	}

	start = TRAN_RECORD_START;

//	if (gunno == 1) {
//		fid = FILE_ID_CHARGE_RD_1;
//		start = TRAN_RECORD_1_START;
//	} else {
//		fid = FILE_ID_CHARGE_RD_0;
//		start = TRAN_RECORD_0_START;
//	}

	len = sizeof(tran_record_nand_ql_h);
	if (flag_finished == _MSG_SAVE_START_) {
		memcpy(rdnand_h.serialnum, g_charge_arg[gunno].serialnum, 32); //交易流水号
		rdnand_h.starttime = g_mtdata_ql[gunno].startChargingtime;
		for (i = 0; i < 5; i++) {
			rdnand_h.w_start[i] = g_realData[gunno].kWh[i];
		}
		rdnand_h.billmode=g_charge_arg[gunno].billmode;
		rdnand_h.startmode=g_charge_arg[gunno].startmode;
		rdnand_h.chargevalue=g_charge_arg[gunno].value;

		len = sizeof(tran_record_nand_ql_h);


		count = app_fs_write(fid, start, len, (u8*) &rdnand_h);

		if(count!=len)
		{
			DEBUG_SHOW1("中间充电数据头数据保存出错！！！！！！！！！！！count=%d  len=%d  rdnand_h.serialnum=%.*a\r\n",count,len,32,rdnand_h.serialnum);
		}
		else
			DEBUG_SHOW1("中间充电数据头数据保存成功！！！！！！！！！！！count=%d  len=%d  \r\n",count,len);
		rdnand.rateid = g_mtdata_ql[gunno].rateid;
		flag_finished = _MSG_SAVE_CHANGE_;
		return 1;

	} else {
		count = app_fs_read(fid, start, len, (u8*) &rdnand_h);//读出数据头

		if (memcmp(rdnand_h.serialnum, g_charge_arg[gunno].serialnum, 32)
				!= 0) {
			DEBUG_SHOW1("中间充电数据无法保存到文件头 flag_finished=%x", flag_finished);
			DEBUG_SHOW1("中间充电数据无法保存到文件头 %.*a  %.*a", 32,
					g_charge_arg[gunno].serialnum, 32, rdnand_h.serialnum);
			DEBUG_SHOW1("中间充电数据无法保存到文件头 %s  %s", g_charge_arg[gunno].serialnum, rdnand_h.serialnum);

			return 1;
		}
		days = getCurDayOfYear(g_mtdata_ql[gunno].startChargingtime.Year,
				g_mtdata_ql[gunno].startChargingtime.Month,
				g_mtdata_ql[gunno].startChargingtime.Day);
	    printf("年初到现在的天数  days=%d\n",days);
		offset = start + days * RD_SIZE;
		len = sizeof(tran_record_nand_ql);

		count = app_fs_read(fid, offset, len, (u8*) &rdnand);


	}


	printf("999999999999999999999999999999999999999  flagflag=%d  offset=%d\n",flagflag,offset);
	rdnand.flag_finished=flag_finished;
	rdnand.soc_start = g_mtdata_ql[gunno].start_soc;
	rdnand.soc_end = g_mtdata_ql[gunno].end_soc;
    ret=0;
	if (rdnand.rateid != g_mtdata_ql[gunno].rateid) {
		DEBUG_SHOW1("发生费率切换！！！！！rdnand.rateid=%d  g_mtdata_ql[gunno].rateid=%d",rdnand.rateid,g_mtdata_ql[gunno].rateid);
		rdnand.rateid = g_mtdata_ql[gunno].rateid;
		rdnand.w = 0;
		ret = 1;

	} else
	{
		DEBUG_SHOW1("没有发生费率切换！！！！");
		rdnand.w = g_mtdata_ql[gunno].curkWh[g_mtdata_ql[gunno].rateid];
	}

	for (i = 0; i < 5; i++) {
		rdnand.w_end[i] = g_realData[gunno].kWh[i];
	}

	rdnand.endtime = g_mtdata_ql[gunno].endChargingtime;


	if (flag_finished == _MSG_SAVE_CHANGE_) {
//       if(ret==1)
		   rdnand.flag_finished = _MSG_SAVE_CHANGE_;

	} else if (flag_finished == _MSG_SAVE_STOP_)
		rdnand.flag_finished = _MSG_SAVE_FIN;
	else
		return 2;
	DEBUG_SHOW1("中间充电数据保存到文件  offset=%d",offset);
	count = app_fs_write(fid, offset, len, (u8*) &rdnand);
	return ret;
}

int SavechargeRecord(u8 gunno,u8 type,u8 stop_reason)//type=0  第一次保存文件和数据库 1  中间充电数据，保存到文件
                                                                      //    2 充电结束，保存到数据库和文件  3 结单，保存到文件和数据库
{
	u8 i;
     int ret;
 	tran_record_ql record;
	TDateTime datetime;
	read_current_datetime(&datetime);

	if(type==0) //第一次保存文件和数据库
	{
	    SaveRdNand(gunno,_MSG_SAVE_START_,&datetime);
	    record.flag_finished=_MSG_SAVE_START_;
	}
	else if(type==1)//中间充电数据，保存到文件
	{

	    ret=SaveRdNand(gunno,_MSG_SAVE_CHANGE_,&datetime);
	    if(ret==1)
	    	record.flag_finished=_MSG_SAVE_CHANGE_;
	    else
	    	 return 0;
	}
	else if(type==2)//充电结束，保存到数据库和文件
	{
		SaveRdNand(gunno,_MSG_SAVE_STOP_,&datetime);
		record.flag_finished=0x66;

	}
	else
		return 1;
//	1本地刷卡终止，2远程终止充电，3充满自动停止，4余额不足，5充电桩故障，6 BMS故障
//	7、急停按钮停止256 其他，
//	高字节 正常上传标识
//	0正常，1通讯故障补传，2停电补传，256其它

      record.guntab=gunno;
	  memcpy(record.serialnum,g_charge_arg[gunno].serialnum,32);//交易流水号
	  record.stop_reason=stop_reason;//g_stopInfo[gunno].MX1;
	  u8 bb=0;
//	  {
		  char xx;

		  int lenlen=strlen((char*)g_charge_arg[gunno].serialnum);
		  xx=g_charge_arg[gunno].serialnum[lenlen-1];
          bb=atoi(&xx);
//	  }

       memset(record.userId,0,8);
       memset(record.cardId,0xff,8);
       record.start_soc=g_mtdata_ql[gunno].start_soc;
       record.end_soc=g_mtdata_ql[gunno].end_soc;
       if(record.flag_finished==0x66)
       {
           printf("SOC  SOC  start=%d  end=%d  g_mtdata_xj[gunid].curkWh[0]=%d  g_mtdata_xj[gunno].curkWh[49]=%d\r\n",
    		      (int)g_mtdata_ql[gunno].start_soc,(int)g_mtdata_ql[gunno].end_soc,(int)g_mtdata_ql[gunno].curkWh[0],(int)g_mtdata_ql[gunno].curkWh[48]);


       }

       for(i=1;i<49;i++)
       {
    	   record.w[i]=g_mtdata_ql[gunno].curkWh[i];
       }
    	 record.w_start=g_mtdata_ql[gunno].kWhStart[0];
    	 record.w_end=g_mtdata_ql[gunno].kWhEnd[0];

    	 record.cost_elec=g_mtdata_ql[gunno].cost_elec;
    	 record.cost_server=g_mtdata_ql[gunno].cost_server;
//	 record.cost_elec[i]=g_mtdata[gunno].cost_elec[i];
    	 record.w[0] = g_mtdata_ql[gunno].kWhEnd[0]-g_mtdata_ql[gunno].kWhStart[0];
    	 record.w[0]=record.w[0]*10+bb;

    	 g_uidata->gunmsg[gunno].curkWh=record.w[0];
         if(record.flag_finished==0x66)
         {

         }

    if( pconfig->devtype==DC)
    {
    	//memset(record.carlogo,0xff,17);
         memcpy(record.carlogo,g_startInfo[gunno].dc.MX21,17);//电动汽车唯一标识
    }
    else
    	memset(record.carlogo,0xff,17);


	record.starttime[0]=byte2bcd(g_mtdata_ql[gunno].startChargingtime.Year/100);
	record.starttime[1]=byte2bcd(g_mtdata_ql[gunno].startChargingtime.Year%100);
	record.starttime[2]=byte2bcd(g_mtdata_ql[gunno].startChargingtime.Month);
	record.starttime[3]=byte2bcd(g_mtdata_ql[gunno].startChargingtime.Day);// | g_mtdata[gunno].startChargingtime.Week<<5;
	record.starttime[4]=byte2bcd(g_mtdata_ql[gunno].startChargingtime.Hour);
	record.starttime[5]=byte2bcd(g_mtdata_ql[gunno].startChargingtime.Min);
	record.starttime[6]=byte2bcd(g_mtdata_ql[gunno].startChargingtime.Sec);


	record.endtime[0]=byte2bcd(g_mtdata_ql[gunno].endChargingtime.Year/100);
	record.endtime[1]=byte2bcd(g_mtdata_ql[gunno].endChargingtime.Year%100);
	record.endtime[2]=byte2bcd(g_mtdata_ql[gunno].endChargingtime.Month);
	record.endtime[3]=byte2bcd(g_mtdata_ql[gunno].endChargingtime.Day);// | g_mtdata[gunno].startChargingtime.Week<<5;
	record.endtime[4]=byte2bcd(g_mtdata_ql[gunno].endChargingtime.Hour);
	record.endtime[5]=byte2bcd(g_mtdata_ql[gunno].endChargingtime.Min);
	record.endtime[6]=byte2bcd(g_mtdata_ql[gunno].endChargingtime.Sec);//交易时间

    record.charge_duration=g_mtdata_ql[gunno].charge_duration;


    record.billmode=g_charge_arg[gunno].billmode;//充电策略0:充满为止（默认）	1:时间控制充电	2:金额控制充电	3:电量控制充电	4:按 SOC 控制充电
    record.chargevalue=g_charge_arg[gunno].value;//充电策略参数时间单位为 1 秒	金额单位为 0.01 元	电量时单位为 0.01kw	SOC 单位为%
    record.startmode=g_charge_arg[gunno].startmode; //1 远程充电 0 卡充电
    record.g_stop_detail=g_stop_detail[gunno];//由于故障发生的停止充电的具体故障编码

    if( record.startmode==0 && record.flag_finished==_MSG_SAVE_STOP_)
    	record.flag_finished=_MSG_SAVE_FIN;
     ret=protocol_updateCD(&record);
    if(ret!=0)
    {
    	 printf("数据库写入失败！！！！！！！！！\r\n");

    	 return 1;
    }
    if(record.flag_finished==0x66  ||(record.flag_finished==0xaa && record.startmode==0))
     {
//    	 printf("充电结束时的电量  record.w[0] = %d g_mtdata_xj[gunno].kWhEnd[0]=%d  g_mtdata_xj[gunno].kWhEnd[0]=%d\n\n"
//    			 ,(int)record.w[0],(int) g_mtdata_xj[gunno].kWhEnd[0],(int)g_mtdata_xj[gunno].kWhEnd[0]);
//		sprintf(_tmp_print_str,"充电交易订单号=%s 订单长度=%d  最后位=%d\n",record.serialnum,lenlen,bb);
//
//		fs_debug_104(_tmp_print_str);
//
//		sprintf(_tmp_print_str,"充电结束时的电量 gunno=%d   record.w[0] = %d  g_mtdata_xj[gunno].kWhStart[0]=%d  g_mtdata_xj[gunno].kWhEnd[0]=%d\n\n"
//				,gunno,(int)record.w[0],(int) g_mtdata_xj[gunno].kWhStart[0],(int)g_mtdata_xj[gunno].kWhEnd[0]);
//		fs_debug_104(_tmp_print_str);

    	   cur_record[gunno]=record;
      	   g_uidata->gunmsg[gunno].curkWh=record.w[0];
     }
    return 0;

}
int  initRdMem(u8 gunno)
{
	Cur_FeeCfg cur_feecfg;
	tran_record_nand_ql rdnand;
	tran_record_nand_ql_h rdnand_h;
	tran_record_xj  record;
    int offset=0;
    int count;
    int start;
	int fid;
	u16 days;
	int i;
	int ret;
    
	fid = FILE_ID_FEECFG;
    
	if(gunno>7)
		gunno=7;
    
	start = FEECFG_START + sizeof(Cur_FeeCfg)*gunno;
	count = app_fs_read(fid, start, sizeof(Cur_FeeCfg), (u8*) &cur_feecfg);
	printf("----------price model count:%d flag:%d\n",count,cur_feecfg.flag);
	if(count==0)
		return 0;
	else if(cur_feecfg.flag != 0xaa55)
		return 0;

	printf("----------price model flag:%d\n",cur_feecfg.flag);
	for(i=0; i<48;i++){
		printf("belate_fee[%d]=%d\t charge_fee[%d]=%d\t service_fee[%d]=%d\n",
				i,cur_feecfg.feecfg.belate_fee[i],i,cur_feecfg.feecfg.charge_fee[i],
				i,cur_feecfg.feecfg.service_fee[i]);
	}

	switch(gunno)
	{
	case 0:
		fid = FILE_ID_CHARGE_RD_0;
		break;
	case 1:
		fid = FILE_ID_CHARGE_RD_1;
		break;
	case 2:
		fid = FILE_ID_CHARGE_RD_2;
		break;
	case 3:
		fid = FILE_ID_CHARGE_RD_3;
		break;
	case 4:
		fid = FILE_ID_CHARGE_RD_4;
		break;

	case 5:
		fid = FILE_ID_CHARGE_RD_5;

		break;
	case 6:
		fid = FILE_ID_CHARGE_RD_6;

		break;

	case 7:
		fid = FILE_ID_CHARGE_RD_7;
		break;
	default:
		gunno=7;
		fid = FILE_ID_CHARGE_RD_7;
		break;

	}
    
	start = TRAN_RECORD_START;

	count = app_fs_read(fid, start, sizeof(tran_record_nand_ql_h), (u8*) &rdnand_h);

	days = getCurDayOfYear(rdnand_h.starttime.Year,rdnand_h.starttime.Month,rdnand_h.starttime.Day);
	offset = start+days*RD_SIZE;
	DEBUG_SHOW1("读出头数据的天数=%d   %d  %d  %d  %s offset=%d\n  ",days,rdnand_h.starttime.Year,rdnand_h.starttime.Month,rdnand_h.starttime.Day,rdnand_h.serialnum,offset);
	count = app_fs_read(fid, offset, sizeof(tran_record_nand_ql),
							(u8*)&rdnand);
	if(count==0)
	{
		printf("count=0 000000000000000000000000000000\n");
		return 1;
	}
	else
	{
		 printf("1111111111111111111111111initRdMem rdnand.flag_finished=%x   %d \r\n", rdnand.flag_finished, sizeof(tran_record_nand_ql_h));
	}
    
	if (rdnand.flag_finished == _MSG_SAVE_CHANGE_ || rdnand.flag_finished == _MSG_SAVE_START_ )
	{

		memcpy(record.serialnum,rdnand_h.serialnum,32);
		DEBUG_SHOW1("serialnum=%.*a" ,32,record.serialnum);
		if(protocol_getCD_bySerialnum(&record)!=0)
		{
			DEBUG_SHOW1("数据库可能出错了，没能读到充电记录  %s",record.serialnum);
			return 1;
		}
	    printf("22222222222222222initRdMem  record.flag_finished=%x\r\n",record.flag_finished);
		if(record.flag_finished==_MSG_SAVE_STOP_  ||record.flag_finished==_MSG_SAVE_FIN )
		{
		       rdnand.flag_finished=_MSG_SAVE_STOP_;
		 	  count = app_fs_write(fid, offset, sizeof(tran_record_nand_ql),
						(u8*)&rdnand);

			DEBUG_SHOW1("充电记录已经保存,不用再次保存,%.*a  flag_finished=%x",16,record.serialnum,record.flag_finished);

			return 2;
		}
		else if(record.guntab!=gunno)
		{
			DEBUG_SHOW1("充电记录已经保存,但枪号发生错误,%s  flag_finished=%x,gunid=%d %d",record.serialnum,record.flag_finished,gunno,record.guntab);
		    return 3;
		}
		printf("3333333333333333333initRdMem  record.flag_finished=%x\r\n",record.flag_finished);
		DEBUG_SHOW1("充电记录 ,%s  flag_finished=%x",record.serialnum,record.flag_finished);

		record.stop_reason = 9;
		record.billmode    = rdnand_h.billmode;
		record.billmode    = rdnand_h.chargevalue;
		record.g_stop_detail = 0;
		record.startmode     = rdnand_h.startmode;

		record.start_soc=rdnand.soc_start;
		record.end_soc=rdnand.soc_end;
		record.endtime[0]=byte2bcd(rdnand.endtime.Year/100);
		record.endtime[1]=byte2bcd(rdnand.endtime.Year%100);
		record.endtime[2]=byte2bcd(rdnand.endtime.Month);
		record.endtime[3]=byte2bcd(rdnand.endtime.Day);// | g_mtdata[gunno].startChargingtime.Week<<5;
		record.endtime[4]=byte2bcd(rdnand.endtime.Hour);
		record.endtime[5]=byte2bcd(rdnand.endtime.Min);
		record.endtime[6]=byte2bcd(rdnand.endtime.Sec);//交易时间

	    record.charge_duration  = diff_DateTime_Min(&rdnand_h.starttime ,&rdnand.endtime);
	    record.w[rdnand.rateid] = rdnand.w;
	    record.w[0] += rdnand.w;
	    record.cost_server = 0;
	    record.cost_elec   = 0;
        
        for (i = 1 ; i < 49; i++)
        {
        	record.cost_server += record.w[i]*cur_feecfg.feecfg.service_fee[i-1];
        	record.cost_elec   += record.w[i]*cur_feecfg.feecfg.charge_fee[i-1];
        }
        
        record.w_start = rdnand_h.w_start[0];
	    record.w_end   = rdnand.w_end[0];

	    record.flag_finished=_MSG_SAVE_STOP_;

	    if(record.startmode == 0)
	    {
	    	record.flag_finished=_MSG_SAVE_FIN;
	    }
        
	    ret = protocol_updateCD(&record);
        
	    if (ret != 0)
	    	 printf("xxxxxxxxxxxxxxxxxxxxxxx\r\n");

	    rdnand.flag_finished=_MSG_SAVE_STOP_;
	 	count = app_fs_write(fid, offset, sizeof(tran_record_nand_ql), (u8*)&rdnand);

	}
	else
	{
		printf("没有需要上传的充电数据！！！！！\r\n");
		return 4;
	}

    return 0;

}

#endif
